//
//  CHJUploadModel.m
//  
//
//  Created by jiaxuzhou on 2017/12/2.
//

#import "CHJUploadModel.h"

#import "FMDatabase.h"
#import "FMDatabaseQueue.h"
#import "CHJUploadVideo.h"
#import <objc/runtime.h>

#define CreateTableSQL    @"CREATE TABLE IF NOT EXISTS uploadVideoIns (\
id INTEGER PRIMARY KEY AUTOINCREMENT,\
suid VARCHAR DEFAULT '',\
token VARCHAR DEFAULT '',\
title VARCHAR DEFAULT '',\
progress VARCHAR DEFAULT '',\
filePath VARCHAR DEFAULT '',\
status VARCHAR DEFAULT '',\
fileName VARCHAR DEFAULT '',\
deviceName VARCHAR DEFAULT '',\
width VARCHAR DEFAULT '',\
height VARCHAR DEFAULT '',\
offsetTime VARCHAR DEFAULT '',\
ext VARCHAR DEFAULT '',\
fileSize VARCHAR DEFAULT '',\
videoLen VARCHAR DEFAULT '',\
thumb VARCHAR DEFAULT '',\
scid VARCHAR DEFAULT '',\
segment VARCHAR DEFAULT '',\
location VARCHAR DEFAULT '',\
locationText VARCHAR DEFAULT '',\
uploadStatTime VARCHAR DEFAULT '',\
source VARCHAR DEFAULT '',\
accessToken VARCHAR DEFAULT '',\
uploadStatus VARCHAR DEFAULT '',\
topic VARCHAR DEFAULT '',\
isChangeThumb  VARCHAR DEFAULT '',\
extInfo VARCHAR DEFAULT '',\
extInfo1 VARCHAR DEFAULT '',\
extInfo2 VARCHAR DEFAULT '',\
extInfo3 VARCHAR DEFAULT '',\
isFinish VARCHAR DEFAULT '',\
storageType VARCHAR DEFAULT '',\
chunkSize VARCHAR DEFAULT '',\
isModified VARCHAR DEFAULT '0',\
isSyncWeibo VARCHAR DEFAULT '0',\
isSyncedWeibo VARCHAR DEFAULT '0',\
isReportedWeiboId VARCHAR DEFAULT '0',\
imageToken VARCHAR DEFAULT '',\
mediaToken VARCHAR DEFAULT '',\
isThumbUploadComplate VARCHAR DEFAULT '0',\
isVideoUploadComplate VARCHAR DEFAULT '0',\
isShareToWeixin VARCHAR DEFAULT '0',\
srwid VARCHAR DEFAULT '',\
isHaveMoney VARCHAR DEFAULT '0',\
giftID VARCHAR DEFAULT '0',\
videoCategory VARCHAR DEFAULT '0',\
orginVideoMD5 VARCHAR DEFAULT '')"

static NSString *kdbPath;

@implementation CHJUploadModel

+ (id)sharedInstance
{
    static CHJUploadModel *uploadModel = nil;
    if (!uploadModel) {
        @synchronized(self) {
            if (!uploadModel) uploadModel = [[CHJUploadModel alloc] initWithDBPath:kdbPath];
        }
    }
    return uploadModel;
}

+ (void)config:(NSString *)dbPath {
    kdbPath = dbPath;
}


- (void)initSqliteDBPath:(NSString *)dbPath {
    _db = [FMDatabaseQueue databaseQueueWithPath:dbPath];
    [_db inDatabase:^(FMDatabase *db) {
        [db executeUpdate:CreateTableSQL];
        [self DBdebug:db];
        
        [db executeUpdate:@"ALTER TABLE uploadVideoIns ADD COLUMN srwid VARCHAR DEFAULT ''"];
        
        [db executeUpdate:@"ALTER TABLE uploadVideoIns ADD COLUMN isHaveMoney VARCHAR DEFAULT '0'"];
        [db executeUpdate:@"ALTER TABLE uploadVideoIns ADD COLUMN giftID VARCHAR DEFAULT ''"];
        [db executeUpdate:@"ALTER TABLE uploadVideoIns ADD COLUMN videoCategory VARCHAR DEFAULT ''"];
        
        [db executeUpdate:@"ALTER TABLE uploadVideoIns ADD COLUMN xinDongFang VARCHAR DEFAULT ''"];
        [db executeUpdate:@"ALTER TABLE uploadVideoIns ADD COLUMN channelformatjson VARCHAR DEFAULT ''"];
        [db executeUpdate:@"ALTER TABLE uploadVideoIns ADD COLUMN strDesc VARCHAR DEFAULT ''"];
        [db executeUpdate:@"ALTER TABLE uploadVideoIns ADD COLUMN strIdfa VARCHAR DEFAULT ''"];
        
        
        //更新新表结构
        //        [db executeUpdate:@"UPDATE uploadVideoIns SET `isModified`=`extInfo1` WHERE `uploadStatTime` > "];
        //        [db executeUpdate:@"UPDATE uploadVideoIns SET `isSyncedWeibo`=`extInfo2`"];
        //        [db executeUpdate:@"UPDATE uploadVideoIns SET `isSyncWeibo`=`extInfo`"];
        
        //        [db executeUpdate:@"UPDATE uploadVideoInsIns SET `filePath`=replace(`filePath`,) WHERE `filePath` LIKE '/var/mobile/Applications/%/Documents/media/'"];
        
        [self DBdebug:db];
    }];
}

- (id)initWithDBPath:(NSString *)dbPath
{
    self = [super init];
    if (self) {
        [self initSqliteDBPath:dbPath];
    }
    return self;
}

- (void)addVideo:(CHJUploadVideo *)video
{
    [_db inDatabase:^(FMDatabase *db) {
        [db executeUpdate:[self insertSQL:video]];
        [self DBdebug:db];
    }];
}

- (void)updateVideo:(CHJUploadVideo *)video
{
    dispatch_semaphore_t semaphore = dispatch_semaphore_create(0);
    [_db inDatabase:^(FMDatabase *db) {
        NSArray *propertys = [self allPropertyNames:video];
        NSMutableDictionary *dictionaryArgs = [NSMutableDictionary dictionary];
        NSMutableArray *segment = [NSMutableArray arrayWithCapacity:0];
        for (NSString *key in propertys) {
            if ([video valueForKey:key] != nil) {
                [dictionaryArgs setObject:[NSString stringWithFormat:@"%@",[video valueForKey:key]] forKey:key];
                [segment addObject:[NSString stringWithFormat:@"`%@`=:%@",key,key]];
            } else {
                [dictionaryArgs setObject:@"" forKey:key];
                [segment addObject:[NSString stringWithFormat:@"`%@`=:%@",key,key]];
            }
        }
        NSString *sql = [@"UPDATE uploadVideoIns SET " stringByAppendingFormat:@"%@ WHERE `filePath` like '%%%@'",[segment componentsJoinedByString:@","],[video.filePath lastPathComponent]];
        [db executeUpdate:sql withParameterDictionary:dictionaryArgs];
        [self DBdebug:db];
        dispatch_semaphore_signal(semaphore);
    }];
    dispatch_semaphore_wait(semaphore, DISPATCH_TIME_FOREVER);
}

- (void)updateVideo:(CHJUploadVideo *)video withField:(NSString *)field
{
    dispatch_semaphore_t semaphore = dispatch_semaphore_create(0);
    [_db inDatabase:^(FMDatabase *db) {
        NSString *segment = [NSString stringWithFormat:@"`%@`=?",field];
        NSString *sql = [@"UPDATE uploadVideoIns SET " stringByAppendingFormat:@"%@ WHERE `filePath` Like '%%%@'",segment,[video.filePath lastPathComponent]];
        [db executeUpdate:sql,[video valueForKey:field]];
        [self DBdebug:db];
        dispatch_semaphore_signal(semaphore);
    }];
    dispatch_semaphore_wait(semaphore, DISPATCH_TIME_FOREVER);
}

- (void)delVideo:(CHJUploadVideo *)video
{
    [_db inDatabase:^(FMDatabase *db) {
        [db executeUpdate:[self deleteSQL:video]];
        [self DBdebug:db];
    }];
}

- (NSArray *)listVideo:(NSString *)where
{
    dispatch_semaphore_t semaphore = dispatch_semaphore_create(0);
    __block NSMutableArray *items = [NSMutableArray arrayWithCapacity:0];
    
    [_db inDatabase:^(FMDatabase *db) {
        FMResultSet *rs = [db executeQuery:[self selectSQL:where]];
        while ([rs next]) {
            CHJUploadVideo *video = [[CHJUploadVideo alloc] initWithDB:[rs resultDictionary]];
            [items addObject:video];
        }
        [rs close];
        [self DBdebug:db];
        dispatch_semaphore_signal(semaphore);
    }];
    
    dispatch_semaphore_wait(semaphore, DISPATCH_TIME_FOREVER);
    return items;
}

- (void)listVideo:(NSString *)where withBlock:(CHJUploadModelBlock)block
{
    [_db inDatabase:^(FMDatabase *db) {
        FMResultSet *rs = [db executeQuery:[self selectSQL:where]];
        NSMutableArray *items = [NSMutableArray arrayWithCapacity:0];
        while ([rs next]) {
            CHJUploadVideo *video = [[CHJUploadVideo alloc] initWithDB:[rs resultDictionary]];
            [items addObject:video];
        }
        [rs close];
        dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{
            block(items);
        });
        [self DBdebug:db];
    }];
}

- (CHJUploadVideo *)refreshVideo:(CHJUploadVideo *)video
{
    CHJUploadVideo *newVideo = nil;
    NSArray *items = [self listVideo:[NSString stringWithFormat:@"`filePath` LIKE '%%%@'",[video.filePath lastPathComponent]]];
    if ([items count]) {
        newVideo = [items objectAtIndex:0];
    }
    return newVideo;
}



- (void)DBdebug:(FMDatabase *) db
{
    //    FMDBQuickCheck([_db hadError]);
    if ([db hadError]) {
        NSLog(@"Err %d: %@", [db lastErrorCode], [db lastErrorMessage]);
    }
}

- (NSArray *)allPropertyNames:(id)model
{
    unsigned count;
    objc_property_t *properties = class_copyPropertyList([model class], &count);
    
    NSMutableArray *rv = [NSMutableArray array];
    
    unsigned i;
    for (i = 0; i < count; i++)
    {
        objc_property_t property = properties[i];
        NSString *name = [NSString stringWithUTF8String:property_getName(property)];
        if (![[[model class] noObProperties] containsObject:name]) {
            [rv addObject:name];
        }
    }
    
    free(properties);
    
    return rv;
}

- (NSString *)insertSQL:(CHJUploadVideo *)model {
    NSArray *propertys = [self allPropertyNames:model];
    NSMutableArray *values = [NSMutableArray arrayWithCapacity:0];
    for (NSString *key in propertys) {
        if ([model valueForKey:key] != nil) {
            [values addObject:[model valueForKey:key]];
        } else {
            [values addObject:@""];
        }
    }
    
    NSString *sql = [NSString stringWithFormat:@" INSERT INTO uploadVideoIns (`%@`) VALUES ('%@')",
                     [propertys componentsJoinedByString:@"`,`"],[values componentsJoinedByString:@"','"]];
    return sql;
}

- (NSString *)uploadSQL:(CHJUploadVideo *)model {
    NSArray *propertys = [self allPropertyNames:model];
    NSMutableArray *values = [NSMutableArray arrayWithCapacity:0];
    for (NSString *key in propertys) {
        if ([model valueForKey:key] != nil) {
            [values addObject:[NSString stringWithFormat:@"`%@`='%@'",key,[model valueForKey:key]]];
        } else {
            [values addObject:[NSString stringWithFormat:@"`%@`='%@'",key,@"''"]];
        }
        
    }
    
    NSString *sql = [NSString stringWithFormat:@" UPDATE uploadVideoIns SET %@ WHERE `filePath` LIKE '%%%@'",
                     [values componentsJoinedByString:@","],[model.filePath lastPathComponent]];
    return sql;
}

- (NSString *)selectSQL:(NSString *)where {
    NSString *sql = [NSString stringWithFormat:@"SELECT * FROM uploadVideoIns WHERE %@ ORDER BY id ASC",where];
    return sql;
}

- (NSString *)deleteSQL:(CHJUploadVideo *)model {
    NSString *sql = [NSString stringWithFormat:@"DELETE FROM uploadVideoIns WHERE `filePath` LIKE '%%%@'",[[model filePath] lastPathComponent]];
    return sql;
}

@end
